﻿using System;
using System.Linq;
using System.Linq.Expressions;

namespace DailyFx.UI
{
	public interface IConfigurationBinding
	{
		/// <summary>
		/// 
		/// </summary>
		PropertyObserver<IConfiguration> CreateConfiguration( IConfiguration config);

		/// <summary>
		/// 
		/// </summary>
		void DeleteConfiguration( IConfiguration config);

		/// <summary>
		/// 
		/// </summary>
		PropertyObserver<IConfiguration> GetConfiguration( IConfiguration config);

		/// <summary>
		/// 
		/// </summary>
		bool ContainsConfiguration( IConfiguration config);

	}


	public static class IConfigurationBindingExtension
	{
		public static void Bind<T>( this IConfigurationBinding binding, IConfiguration configuration, 
			Expression<Func<T, object>> propertyExpression, Action<IConfiguration> handler)
		{
			// convert an expression into a method .
			var lambda = (LambdaExpression) propertyExpression;
			MemberExpression member;
			if (lambda.Body is UnaryExpression)
			{
				var unary = (UnaryExpression)lambda.Body;
				member = (MemberExpression)unary.Operand;
			}
			else
			{
				member = (MemberExpression) lambda.Body;
			}
			string propertyName = member.Member.Name;
			//
			Bind( binding, configuration, propertyName, handler);
		}

		public static void Bind( this IConfigurationBinding binding, IConfiguration configuration, 
			String propertyName, Action<IConfiguration> handler )
		{
				var c = binding.GetConfiguration( configuration);
				c.RegisterHandler( propertyName, handler);
		}

		public static void Unbind<T>( this IConfigurationBinding binding, 
			IConfiguration configuration, Expression<Func<T, object>> propertyExpression )
		{
			// convert an expression into a method .
			var lambda = (LambdaExpression)propertyExpression;
			MemberExpression member;
			if (lambda.Body is UnaryExpression)
			{
				var unary = (UnaryExpression)lambda.Body;
				member = (MemberExpression)unary.Operand;
			}
			else
			{
				member = (MemberExpression)lambda.Body;
			}
			string propertyName = member.Member.Name;
			//
			Unbind(binding, configuration, propertyName);
		}

		public static void Unbind ( this IConfigurationBinding binding, 
			IConfiguration configuration, string propertyName )
		{
			var c = binding.GetConfiguration(configuration );
			c.UnregisterHandler(propertyName);
		}
	}

}
